package service

import (
	"go-im/src/helper"
	"go-im/src/model"
	"log"
	"net/http"
	"time"

	"github.com/gin-gonic/gin"
	"github.com/gorilla/websocket"
)

var upgrader = websocket.Upgrader{}
var wc = make(map[string]*websocket.Conn)

func WebsocketMessage(c *gin.Context) {
	conn, err := upgrader.Upgrade(c.Writer, c.Request, nil)
	if err != nil {
		c.JSON(http.StatusOK, gin.H{
			"code": -1,
			"msg":  "server internal error: " + err.Error(),
		})
		return
	}

	defer conn.Close()

	uc := c.MustGet("user_claims").(*helper.UserClaim)
	wc[uc.Identity] = conn
	for {
		ms := new(helper.MessageStruct)
		err := conn.ReadJSON(ms)
		if err != nil {
			log.Println("read error: ", err)
			return
		}

		_, err = model.GetUserRoomByUserIdentityRoomIdentity(uc.Identity, ms.RoomIdentity)
		if err != nil {
			log.Printf("UserIdentity: %v RoomIdentity: %v not exists\n", uc.Identity, ms.RoomIdentity)
			return
		}

		mb := &model.MessageBasic{
			UserIdentity: uc.Identity,
			RoomIdentity: ms.RoomIdentity,
			Data:         ms.Message,
			CreatedAt:    time.Now().Unix(),
			UpdatedAt:    time.Now().Unix(),
		}

		err = model.InsertOneMessageBasic(mb)
		if err != nil {
			log.Println("failed to insert one message basic: ", err)
			return
		}

		userRooms, err := model.GetUserRoomByRoomIdentity(ms.RoomIdentity)
		if err != nil {
			log.Println("failed to get user rooms: ", err)
			return
		}

		for _, room := range userRooms {
			if cc, ok := wc[room.UserIdentity]; ok {
				err := cc.WriteMessage(websocket.TextMessage, []byte(ms.Message))
				if err != nil {
					log.Println("write message error: ", err)
					return
				}
			}
		}
	}
}
